home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
Internet Info 1994 March
/
Internet Info CD-ROM (Walnut Creek) (March 1994).iso
/
networking
/
ip
/
ka9q
/
MNetsrc.hqx
/
Mac TCP_IP Source v.33
/
mac_io.c
< prev
next >
Wrap
Text File
|
1989-03-14
|
10KB
|
486 lines
/*mac_io.c
* machine dependent serial I/O stuff for Macintosh
* (also contains overall Macintosh I/O initialization)
*/
#include <stdio.h>
#include "global.h"
#include "iface.h"
#include "mac.h"
#include "mac_files.h"
#include <SerialDvr.h>
#include <time.h>
struct Store_input Store_input[ASY_MAX];
struct asy asy[ASY_MAX];
static ioParam MacSer;
struct interface *ifaces;
struct RemoveIt Head;
unsigned nasy;
/* Called at startup time to set up console I/O, memory heap */
ioinit()
{
/* in unix library, long timezone is the difference between GMT and this
* time zone. tzname[0] is set to "EST", tzname[1] is set to "EDT".
* We leave these alone. There ought to be an option in NET.START to change
* these parameters.
*/
Click_On(1); /* want the LSC EXIT window when we leave */
mac_files(1); /* do the file init stuff */
return(0);
}
/* Called just before exiting to restore console state */
iostop()
{
int i;
struct RemoveIt *tp,*tp1;
WindowPeek wRec;
WindowPtr wind;
Click_On(0); /* Disable "click to continue" */
/*
Close all application and DA windows that are open when
we leave the application. In MultiFinder, DA's are not
effected since they don't reside in the application layer.
*/
while ( FrontWindow() != NULL ){
wRec = (WindowPeek)FrontWindow();
if ((wRec->windowKind==dialogKind) || (wRec->windowKind==userKind))
HideWindow(FrontWindow()); /* nuke 'em */
else
CloseDeskAcc(wRec->windowKind);
}
while(ifaces != NULLIF) {
if(ifaces->stop != NULLFP)
(*ifaces->stop)(ifaces);
ifaces = ifaces->next;
}
/*
* I want to close down all the files and then remove the (possibly still existing)
* files because the MAC will not allow the file to be removed when it still has an
* open file descriptor
*/
for( i = 3; i < _NFILE; i++)
{
close(i);
}
unlink(dirnet);
/* get our first entry, delete string but leave structure with null pointer */
tp = &Head;
if (tp->name_ptr != NULL) {
(void)unlink(tp->name_ptr);
(void)free(tp->name_ptr);
}
tp1 = tp->next; /* prepare for loop that follows */
tp->next = NULL; /* initialize pointer to next entry */
tp->name_ptr = NULL; /* initialize string pointer */
/* now traverse list */
while(tp1 != NULL) {
tp = tp1; /* get pointer to current entry */
tp1 = tp->next; /* prepare pointer to next entry */
if (tp->name_ptr != NULL) {
(void)unlink(tp->name_ptr);
(void)free(tp->name_ptr);
}
(void)free(tp);
}
}
/* Initialize asynch port "dev" */
int slipisopen = 0;
SerShk HandShake;
int
asy_init(dev,arg1,arg2,bufsize)
int16 dev;
unsigned bufsize;
char *arg1,*arg2;
{
register struct asy *ap;
register struct interface *if_asy;
extern struct interface *ifaces;
struct Store_input *store;
OsErr e;
char *Recv_buf;
char *Send_buf;
ap = &asy[dev];
#ifdef DEBUG
printf("asy_init: as->tty = %s, dev = %d.\n", ap->tty, dev);
#endif
if ( ap == NULL)
return(-1);
Recv_buf = malloc(bufsize);
if(Recv_buf == NULL) {
printf("asy_init: memory allocation error - Recv_buf.\n");
exit(-1);
}
Send_buf = malloc(bufsize);
if(Send_buf == NULL) {
printf("asy_init: memory allocation error - Send_buf.\n");
exit(-1);
}
ap->recv_buf = malloc(bufsize);
if(ap->recv_buf == NULL) {
printf("asy_init: memory allocation error - ap->recv_buf.\n");
exit(-1);
}
/*
* the user can use either port 'a' or 'b'. 'A' is the preferred
*/
switch ( *arg2 )
{
case 'a':
case 'A':
if ( ap->devopen == 0 ) {
if ( (e = RAMSDOpen(sPortA)) != noErr ) {
printf("asy_init: RAMSDOpen failed, e = %d.\n",e);
exit(-1);
}
ap->portIn = AinRefNum;
ap->portOut = AoutRefNum;
ap->devopen = 1;
}
else {
printf("asy_init: Device %c is already open.\n", ap->tty[0]);
return(-1);
}
break;
case 'b':
case 'B':
if ( ap->devopen == 0) {
if ( (e = RAMSDOpen(sPortB)) != noErr ) {
printf("asy_init: RAMSDOpen failed, e = %d.\n", e);
exit(-1);
}
ap->portIn = BinRefNum;
ap->portOut = BoutRefNum;
ap->devopen = 1;
}
else {
printf("asy_init: Device %c is already open.\n", ap->tty[0] );
return(-1);
}
break;
default:
printf("asy_init: Unknown device %c, could not configure port.\n", ap->tty);
return(-1);
}
/* setup the ring buffer for input on this device */
store = &Store_input[dev];
store->store = malloc(bufsize);
if(store->store == NULL) {
printf("asy_init: memory allocation error - Store_input.\n");
exit(-1);
}
store->head = store->store;
store->tail = store->store;
store->amt = 0;
store->bufsize = bufsize;
/*
* tell the device that it can receive only bufsize
*/
if ( SerSetBuf( ap->portIn, Recv_buf, bufsize) != noErr) {
printf("asy_init: SerSetBuf error on %d.\n", ap->portIn);
exit(-1);
}
if ( SerSetBuf( ap->portOut, Send_buf, bufsize) != noErr) {
printf("asy_init: SerSetBuf error on %d.\n", ap->portOut);
exit(-1);
}
HandShake.fXOn = FALSE; /* Setup handshake parms */
HandShake.fCTS = FALSE;
HandShake.xOn = 0x11;
HandShake.xOff = 0x13;
HandShake.errs = 0;
HandShake.evts = 0;
HandShake.fInX = FALSE;
HandShake.fDTR = 0;
if (ap->addr == 1)
HandShake.fCTS = TRUE;
slipisopen = 1;
return (0);
}
int
asy_stop(interface)
struct interface *interface;
{
register struct asy *ap;
ap = &asy[interface->dev];
if (slipisopen) {
/*
* kill off any io pending
*/
MacSer.ioActCount = 0;
MacSer.ioRefNum = ap->portIn;
MacSer.ioCompletion = 0;
MacSer.ioBuffer = ap->recv_buf;
MacSer.ioReqCount = 0;
MacSer.ioPosMode = 1;
PBKillIO(&MacSer, FALSE);
if ( ap->portIn = AinRefNum)
RAMSDClose(sPortA);
else
RAMSDClose(sPortB);
slipisopen = 0;
}
}
/* Asynchronous line I/O control */
asy_ioctl(interface,argc,argv)
struct interface *interface;
int argc;
char *argv[];
{
if(argc < 1) {
printf("%d\r\n",asy[interface->dev].speed);
return 0;
}
return asy_speed(interface->dev,atoi(argv[0]));
}
/* Set asynch line speed */
int
asy_speed(dev,speed)
int dev;
int speed;
{
int serialconfig;
struct asy *ap;
ap = &asy[dev];
if(speed == 0 || dev >= nasy)
return(-1);
#ifdef DEBUG
printf("asy_speed: Setting speed for device %d to %d\n",dev, speed);
#endif
asy[dev].speed = speed;
switch(speed)
{
case 300:
serialconfig = baud300;
break;
case 600:
serialconfig = baud600;
break;
case 1200:
serialconfig = baud1200;
break;
case 1800:
serialconfig = baud1800;
break;
case 2400:
serialconfig = baud2400;
break;
case 3600:
serialconfig = baud3600;
break;
case 4800:
serialconfig = baud4800;
break;
case 7200:
serialconfig = baud7200;
break;
case 9600:
serialconfig = baud9600;
break;
case 19200:
serialconfig = baud19200;
break;
case (long)57600:
serialconfig = baud57600;
break;
default:
printf("asy_speed: Unknown speed (%ld)\n", speed);
break;
}
#ifdef DEBUG
printf("serialconfig = %d\n", serialconfig);
#endif
serialconfig |= (stop10|noParity|data8);
/* not set the speed up */
if ( SerReset( ap->portIn, serialconfig) != noErr) {
printf("asy_speed: could not set config for %d.\n", ap->portIn);
exit(-1);
}
if ( SerHShake(ap->portIn, &HandShake) != noErr) {
printf("asy_speed: could not set handshake for %d.\n", ap->portIn);
exit(-1);
}
if ( SerReset( ap->portOut, serialconfig) != noErr) {
printf("asy_speed: could not set config for %d.\n", ap->portOut);
exit(-1);
}
if ( SerHShake(ap->portOut, &HandShake) != noErr) {
printf("asy_speed: could not set handshake for %d.\n", ap->portOut);
exit(-1);
}
#ifdef DEBUG
printf("asy_speed: completed.\n");
#endif
return(0);
}
/* Send a buffer to serial transmitter */
asy_output(dev,buf,cnt)
unsigned dev;
char *buf;
unsigned short cnt;
{
register struct asy *ap;
long amount = (long)cnt;
ap = &asy[dev];
#ifdef DEBUG
printf("asy_output called. dev = %x, cnt = %d\n", dev, cnt);
#endif
if(dev >= nasy)
return(-1);
FSWrite(ap->portOut,&amount, buf);
return(0);
}
/*
* Receive characters from asynch line
* Returns count of characters read
*/
unsigned
asy_recv(dev,buf,cnt)
int dev;
char *buf;
unsigned cnt;
{
long amount[8];
int tot = 0;
struct Store_input *store;
int got = 0;
int tt;
struct asy *ap;
#ifdef DEBUG
printf("asy_recv: dev = %d\n", dev);
#endif
if ( dev > nasy ) {
printf("asy_recv: Error on receive. dev = %d, max = %d\n", dev, nasy);
exit(-1);
}
ap = &asy[dev];
store = &Store_input[dev]; /* point to current */
if ( cnt > 0 && store->amt > 0) {
tt = min(cnt,store->amt);
tt = min(tt,store->bufsize);
got = 0;
while ( tt-- > 0) {
buf[got++] = *store->tail++;
if ( store->tail >= &store->store[store->bufsize])
store->tail = store->store; /* wrap around */
if ( got >= cnt )
break;
}
store->amt -= got;
return( got );
}
else
if ( cnt == 0 )
return(0);
/*
* How much is waiting for us? If any is waiting, this go and get it
*/
Status( ap->portIn, 2, &amount[0]);
if ( amount[0] > 0L) {
MacSer.ioRefNum = ap->portIn;
MacSer.ioCompletion = 0;
MacSer.ioBuffer = ap->recv_buf;
MacSer.ioReqCount = (amount[0] < store->bufsize) ? amount[0] : store->bufsize;
MacSer.ioPosMode = 1;
tot = PBRead(&MacSer, FALSE);
if ( MacSer.ioResult != noErr)
printf("asy_recv: Read failed. Device = %d.\n",dev);
tt = MacSer.ioActCount;
got = 0;
while (tt-- > 0) {
*store->head++ = ap->recv_buf[got++];
if ( store->head == &store->store[store->bufsize] ) {
/* printf("xx got wrap\n"); */
store->head = store->store;
}
store->amt++;
}
if ( cnt > 0 && store->amt > 0) {
tt = min(cnt,store->amt);
tt = min(tt,store->bufsize);
got = 0;
/*
* now store it in the ring buffer
*/
while ( tt-- > 0) {
buf[got++] = *store->tail++;
if ( store->tail >= &store->store[store->bufsize])
store->tail = store->store; /* wrap around */
if ( got >= cnt )
break;
}
store->amt -= got;
return( got );
}
return ( 0 );
}
return (got);
}